import json
import logging
import os
import shutil
import time
from contextlib import asynccontextmanager

from fastapi import FastAPI
from fastapi import Request
from fastapi import Response

from api.fm.core.Ioc.base import get_container
from api.fm.libs.net import net_utils

logger = logging.getLogger(__name__)

box = get_container()


@asynccontextmanager
async def lifespan(app: FastAPI):
    # 启动时的代码
    print("Application is starting up")
    yield
    # 关闭时的代码
    shutil.rmtree(os.environ.get('TEMP_DIR'), ignore_errors=True)
    print("Application is shutting down")


# 初始化web服务
app = FastAPI(
    title="api接口",
    description="FastAPI",
    version="0.0.1",
    lifespan=lifespan,
    root_path="/api",
)


@app.middleware("http")
async def request_log(request: Request, call_next):
    """中间件: 请求 来源 时间"""
    start_time = time.time()
    request_ip = net_utils.NetUtil.get_request_ip(request)
    method = request.method
    url = request.url.path
    query_params = dict(request.query_params)
    try:
        # 尝试获取 JSON 请求体
        json_body = await request.json()
    except json.JSONDecodeError:
        # 如果不是 JSON 格式，尝试获取原始请求体
        json_body = await request.body()
        json_body = json_body.decode('utf-8') if isinstance(json_body, bytes) else json_body
    except Exception as e:
        # 记录其他异常
        logger.error(f"Error parsing request body: {e}")
        json_body = None

    logger.info(
        f"↘ {request_ip} <{method}> {url} -> query: {query_params} -> body: {json_body}"
    )

    response: Response = await call_next(request)

    end_time = time.time()
    timer = end_time - start_time

    logger.info(
        f"↗ {request_ip} <{method}> {url} -> status: {response.status_code} -> duration: {timer:.4f}s"
    )
    return response
